#version 320 es
precision mediump float;

uniform sampler2D u_gPosition;
uniform sampler2D u_gNormal;
uniform sampler2D u_gAlbedoSpec;

out vec4 fragColor;
in vec2 v_TexCoord;

struct Light {
    vec3 Position;
    vec3 Color;
};

const int NR_LIGHTS = 2;
uniform Light u_lights[NR_LIGHTS];
uniform vec3 u_viewPos;

/**
*   @brief 实现反射向量的计算 公式：reflect(I,N)=I−2(I⋅N)N
*/
vec3 myReflect(vec3 I, vec3 N) {
    return I - 2.0 * dot(I, N) * N; // 根据公式计算反射向量
}

void main() {
    // 从G缓冲中获取数据
    vec3 FragPos = texture(u_gPosition, v_TexCoord).rgb;
    vec3 Normal = texture(u_gNormal, v_TexCoord).rgb;
    vec3 Albedo = texture(u_gAlbedoSpec, v_TexCoord).rgb;
    float specularStrength = texture(u_gAlbedoSpec, v_TexCoord).a;

    // 然后和往常一样地计算光照
    float ambientStrength = 0.1;
    vec3 lighting = Albedo * ambientStrength; // 硬编码环境光照分量
    vec3 viewDir = normalize(u_viewPos - FragPos);

    for(int i = 0; i < NR_LIGHTS; ++i)
    {

        // 漫反射
        vec3 lightDir = normalize(u_lights[i].Position - FragPos);
        vec3 diffuse = max(dot(Normal, lightDir), 0.0) * u_lights[i].Color;

        vec3 reflectDir = myReflect(-lightDir, normalize(Normal));     // reflect函数要求第一个向量是从光源指向片段位置的向量
        float spec = pow(max(dot(viewDir, reflectDir), 0.0), 32.0);
        vec3 specular = specularStrength * spec * u_lights[i].Color;

        lighting += (diffuse + specular) * Albedo;
    }

    fragColor = vec4(lighting, 1.0);
}